/**
 * 功能：32位代码，完成多任务的运行
 *
 *创建时间：2022年8月31日
 *作者：李述铜
 *联系邮箱: 527676163@qq.com
 *相关信息：此工程为《从0写x86 Linux操作系统》的前置课程，用于帮助预先建立对32位x86体系结构的理解。整体代码量不到200行（不算注释）
 *课程请见：https://study.163.com/course/introduction.htm?courseId=1212765805&_trace_c_p_k2_=0bdf1e7edda543a8b9a0ad73b5100990
 */
#include "os.h"

typedef unsigned char   uint_8;
typedef unsigned short  uint_16;
typedef unsigned int    uint_32;

#define MAP_ADDRESS     0x80000000  //定义模拟映射的地址，将0x80000000 通过分页机制 从线性空间映射到物理空间
uint_8 map_phy_buffer[4096] __attribute__((aligned(4096))) = {0x36};  //定义待映射的buffer 

//创建GPT 表 
typedef struct gdt_item
{
        uint_16 a;
        uint_16 b;
        uint_16 c;
        uint_16 d;   
}GDT_ITEM_T;

GDT_ITEM_T 
gdt_table[256] __attribute__((aligned(8))) = 
{      
        [0] = {0},
        [KERNEL_CODE_SEG / 8] = {0xffff, 0x0000, 0x9a00, 0x00cf},       //参见intel 官方手册配置，这里并没有解释
        [KERNEL_DATA_SEG / 8] = {0xffff, 0x0000, 0x9200, 0x00cf},
};

//创建页目录表 和 页表
uint_32
pg_table[1024] __attribute__((aligned(4096))) = 
{      
        [0] = 0x0000,
        //[(MAP_ADDRESS >> 12) & 0x3ff] = (uint_32)(map_phy_buffer) | pg_pr | pg_us | pg_rw,
        
};

uint_32
pg_dir_table[1024] __attribute__((aligned(4096))) = 
{      
        [0] = 0 | pg_pr | pg_us | pg_rw | pg_4m,
        //[511] = (uint_32)(pg_table) | pg_pr | pg_us | pg_rw, 
        
};

void page_init(void)
{
    pg_table[(MAP_ADDRESS >> 12) & 0x3ff] = (uint_32)map_phy_buffer | pg_pr | pg_us | pg_rw;
    pg_dir_table[MAP_ADDRESS >> 22] = (uint_32)pg_table | pg_pr | pg_us | pg_rw ;
}
